#pragma once
#include <string>
#include <vector>

#include "../XMLParser/xmlParser.h"
#include "PortalBrowser.h"

class CPortalBrowserSettings
{
	public:
		enum DefinedFlags
		{
			F_NONE                          = 0x00000000,
			F_DISABLE_AUTH_DLG              = 0x00000001,
			F_DISABLE_HUB_LOGIN             = 0x00000002,
			F_SHOW_REQUEST_DUMPER           = 0x00000004,
			F_SHOW_REQUEST_DUMPER_ON_START  = 0x00000008,
			F_DISABLE_AUTOUPDATE            = 0x00000010,
			F_ALLOW_EXTERNAL_LINKS          = 0x00000020,
			F_DENY_NEW_WND                  = 0x00000040,
			F_DENY_EXTERNAL_LINKS_NEW_WND   = 0x00000080,
			F_HOST_TOOLBAR_ICON_FIRST       = 0x00000100,
			F_ENABLE_SCRIPT_DEBUGGING       = 0x00000200,
			F_DISABLE_TOOLBAR_FOLLOW_URL    = 0x00000400,
			F_ALL_LINKS_IN_NEW_WND          = 0x00000800,
			F_HOST_TOOLBAR_ICON_NONE        = 0x00001000,
			F_DISABLE_TOOLBAR               = 0x00002000,
			F_HOST_MENU_NONE                = 0x00004000,
		};
		
		enum DefinedCharset {CH_ANSI, CH_UTF8};
		enum DefinedErrorValues {ERROR_NONE, ERROR_PARSING, ERROR_VERSION};
		
		struct SECTION_STRUCT
		{
			SECTION_STRUCT():
				//SearchRequestMethod(METHOD_DEFAULT),
				iToolbarID(-1),
				Charset(CH_ANSI)
			{
			}
			
			std::wstring strName;
			std::wstring strURL;
			
			std::wstring strSearchCommand;
			
			// optional parameters.
			// if not specified, used default params
			std::wstring strSearchURL;
			std::wstring strSearchName;
			//DefinedRequestMethod SearchRequestMethod;
			DefinedCharset Charset;
			
			int iToolbarID;
			int iSearchbarID;
		};
		
		struct SECTION_NODE;
		typedef std::vector<SECTION_NODE> tSECTION_TREE;
		
		struct SECTION_NODE
		{
			SECTION_STRUCT Section;
			tSECTION_TREE ChildNode;
		};
		
	protected:
	
		tSECTION_TREE m_Section;
		
		std::wstring m_strLoginURL;
		std::wstring m_strLoginCommand;
		//DefinedRequestMethod m_LoginRequestMethod;
		
		std::wstring m_strDefaultSearchURL;
		//std::wstring m_strDefaultSearchCommand;
		//DefinedRequestMethod m_DefaultSearchRequestMethod;
		
		//std::wstring m_strToolbarImageFile;
		//std::wstring m_strSearchbarImageFile;
		HIMAGELIST m_hImageListLarge;
		HIMAGELIST m_hImageListSmall;
		
		DefinedMagnetAction m_MagnetAction;
		size_t m_szDefaultSectionID;
		DWORD m_Flags;
		
		bool m_bCanLogin;
		
		void LoadSectionTree(std::wstring &strPortalURL, XMLParser::XMLNode const &xParameterNode, tSECTION_TREE &node, DefinedCharset DefaultCharset);
		static void ParseFlag(XMLParser::XMLNode &xNode, LPCWSTR FlagName, int FlagVal, DWORD &dwFlags);
		static DWORD SetFlags(XMLParser::XMLNode &xNode, DWORD dwFlags);
		
		void ParsePortalSettings(XMLParser::XMLNode &xPortalNode, HINSTANCE hInstance, std::wstring &strCurDir, std::wstring &strPortalURL, std::wstring &strLoginUser, std::wstring &strLoginPassword, DefinedCharset DefaultCharset);
		
		size_t EnumSectionFindURL(LPCWSTR pszURL, size_t dwURLLen, tSECTION_TREE const *pNode, size_t dwMatch, SECTION_NODE const **ppStruct);
		
	public:
		CPortalBrowserSettings();
		
		DefinedErrorValues LoadSettings(HINSTANCE hInstance, LPCWSTR pszPortalName, LPCWSTR pszLogin, LPCWSTR pszPassword);
		
		__declspec(property(get = GetLoginURL)) std::wstring const &LoginURL;
		__declspec(property(get = GetLoginCommand)) std::wstring const &LoginCommand;
		//__declspec(property(get = GetLoginRequestMethod)) DefinedRequestMethod LoginRequestMethod;
		
		__declspec(property(get = GetSectionCount)) size_t SectionCount;
		__declspec(property(get = GetSection)) SECTION_NODE const Section[];
		
		__declspec(property(get = GetDefaultSearchURL)) std::wstring const &DefaultSearchURL;
		//__declspec(property(get = GetDefaultSearchRequestMethod)) DefinedRequestMethod DefaultSearchRequestMethod;
		
		//__declspec(property(get = GetToolbarFile)) std::wstring const &ToolbarFile;
		//__declspec(property(get = GetSearchbarFile)) std::wstring const &SearchbarFile;
		__declspec(property(get = GetImageListLarge)) HIMAGELIST ImageListLarge;
		__declspec(property(get = GetImageListSmall)) HIMAGELIST ImageListSmall;
		__declspec(property(get = GetDefaultSectionID)) size_t DefaultSectionID;
		
		__declspec(property(get = GetMagnetAction)) DefinedMagnetAction MagnetAction;
		
		__declspec(property(get = GetFlags)) DWORD Flags;
		
		std::wstring const &GetLoginURL()
		{
			return m_strLoginURL;
		}
		
		std::wstring const &GetLoginCommand()
		{
			return m_strLoginCommand;
		}
		
		size_t GetSectionCount()
		{
			return m_Section.size();
		}
		
		SECTION_NODE const &GetSection(size_t ind)
		{
			if (ind >= m_Section.size())
				ind = 0;
				
			return m_Section[ind];
		}
		
		std::wstring const &GetDefaultSearchURL()
		{
			return m_strDefaultSearchURL;
		}
		
		/*
		std::wstring const &GetToolbarFile()
		{
		  return m_strToolbarImageFile;
		}
		
		std::wstring const &GetSearchbarFile()
		{
		  return m_strSearchbarImageFile;
		}
		*/
		
		HIMAGELIST GetImageListLarge()
		{
			return m_hImageListLarge;
		}
		
		HIMAGELIST GetImageListSmall()
		{
			return m_hImageListSmall;
		}
		
		size_t GetDefaultSectionID()
		{
			return m_szDefaultSectionID;
		}
		
		DefinedMagnetAction GetMagnetAction()
		{
			return m_MagnetAction;
		}
		
		DWORD GetFlags()
		{
			return m_Flags;
		}
		
		bool CanLogin()
		{
			return m_bCanLogin;
		}
		
		struct SEARCH_DATA_STRUCT_INTERNAL
		{
			SEARCH_DATA_STRUCT Data;
			std::wstring strName;
		};
		
		struct PORTAL_INFO
		{
			std::wstring strName;
			std::wstring strAssociatedHubURL;
			
			typedef std::vector<SEARCH_DATA_STRUCT_INTERNAL> tSEARCH_DATA;
			
			tSEARCH_DATA Search;
			
			IPortalList::PORTAL_DATA Data;
			
			HBITMAP hLargeBMP;
			HBITMAP hSmallBMP;
		};
		
		typedef std::vector<PORTAL_INFO> tPORTAL_LIST;
		static tPORTAL_LIST GetPortalsList();
		
		bool GetSearchString(SECTION_NODE const *pNode, LPCWSTR pszQuery, std::wstring &strURL, std::wstring &strCommand);
		bool GetLoginString(std::wstring &strLoginString, std::wstring &strLoginCommand);
		
		std::wstring UrlEncode(LPCWSTR pszString, DefinedCharset DefaultCharset);
		size_t FindSectionByURL(LPCWSTR pszURL, SECTION_NODE const **ppStruct);
};